
package org.zerta.troops.client;

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenuItem;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JToolBar;
import javax.swing.JButton;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;

import org.zerta.troops.network.TroopsNetworkClient;
import org.zerta.troops.utilities.StringFromFile;
import org.zerta.troops.xml.WorldProcessor;
import org.zerta.troops.client.GamePanel;
import org.zerta.troops.common.Strings;
import org.zerta.troops.common.World;


/**
 * TODOs:
 * - Handle resizing!
 * 
 * @author martinal
 *
 */
public class AppFrame extends JFrame implements ActionListener, ChangeListener {

	static final long serialVersionUID = 1L;

	// Network client to communicate with server
	private TroopsNetworkClient troopsNetworkClient;

	// Controller object with functionality to modify the model World
	private GameController controller;

    // General GUI components connected to this frame
	private JMenuBar menubar;
	private JToolBar toolbar;
	private JLabel statusbar;

    // Central panels for each game state
	private LobbyPanel setupPanel;
	private GamePanel gamePanel;

    public AppFrame() {
        super(Strings.frameTitle);

        // TODO: Ask to save first.
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
        
        // Setup general GUI stuff
        setLayout(new BorderLayout());
        defineActions();
        defineMenus();
        defineToolbar();
        defineStatusbar();

        // Create network client
        troopsNetworkClient = new TroopsNetworkClient();
        
        // Start game with setup screen
        setupPanel = new LobbyPanel(troopsNetworkClient);
        getContentPane().add(setupPanel, BorderLayout.CENTER);
        pack();
        setVisible(true);
        
        // Show welcome message
        message("Welcome to Troops!");
    }

    /**
     * Switch to in-game mode.
     */
    void beginGame()
    {
        // Load a world
    	message("Loading world...");
    	String mapFile = setupPanel.getMapFilename();
		String mapString = StringFromFile.readStringFromFile(mapFile);
		WorldProcessor mp = new WorldProcessor();
		World world = mp.processMapInput(mapString);

		// Create a controller for this world
    	controller = new GameController(world, troopsNetworkClient);

		// Update GUI
        assert(isAncestorOf(setupPanel));
    	remove(setupPanel);
    	
    	gamePanel = new GamePanel(controller);
        
    	getContentPane().add(gamePanel, BorderLayout.CENTER);
        pack();
    	message("Done loading world.");
    }

    private void defineActions()
    {
    	// TODO: Define actions that can be used by menu, toolbar and other gui components.
    }

    /**
     * Setup menubar for this frame. We may want to
     * modify it depending on the game state later.
     */
    private void defineMenus() {
    	// TODO: Listen to menu actions!
    	menubar = new JMenuBar();

        JMenu file = new JMenu("File");
        JMenuItem item;
        file.add(item = new JMenuItem("New"));
        item.addActionListener(this);
        file.add(item = new JMenuItem("Open"));
        item.addActionListener(this);
        file.addSeparator();
        file.add(item = new JMenuItem("Exit"));
        item.addActionListener(this);
        menubar.add(file);
 
        setJMenuBar(menubar);
    }

    /**
     * Setup toolbar for this frame. We may want to
     * modify it depending on the game state later.
     */
    private void defineToolbar() {
        // TODO: Add something useful here, add listeners

        toolbar = new JToolBar();

        JButton myButton = new JButton("Start game");
        toolbar.add(myButton);
        myButton.addActionListener(this);

        //Icon tigerIcon = new ImageIcon("SmallTiger.gif");
        //myButton = new JButton(tigerIcon);
        //toolbar.add(myButton);

        //toolbar.addSeparator();

        //toolbar.add(new Checkbox("Not"));

        getContentPane().add(toolbar, BorderLayout.NORTH);
    }

    /**
     * Setup statusbar for this frame.
     */
    private void defineStatusbar() {
        statusbar = new JLabel(); // TODO: Is there a better status bar available?
        getContentPane().add(statusbar, BorderLayout.SOUTH);
    }

    /**
     * Show a new message in the status bar.
     */
    public void message(String msg) {
	    statusbar.setText(msg);
	}

    /**
     * Show an new warning message in the status bar.
     */
    public void warning(String msg) {
	    statusbar.setText("WARNING: " + msg);
	}

    /**
     * Show an new error message in the status bar.
     */
    public void error(String msg) {
	    statusbar.setText("ERROR: " + msg);
	}

	@Override
	public void actionPerformed(ActionEvent e) {
		// TODO: Trigger this on event from LobbyPanel
		beginGame(); // currently there's only one toolbar button that triggers this
	}

    public Dimension getPreferredSize() {
        return new Dimension(1024, 768);
    }

	@Override
	public void stateChanged(ChangeEvent e) {
		repaint();
	}

}

